Skip to content

Allow retrying git commits without signing when signing fails#4219

Open
tim-smart wants to merge 5 commits into
pingdotgg:mainfrom
tim-smart:t3code/git-signing-toggle
Open

Allow retrying git commits without signing when signing fails#4219
tim-smart wants to merge 5 commits into
pingdotgg:mainfrom
tim-smart:t3code/git-signing-toggle

Conversation

@tim-smart

@tim-smart tim-smart commented Jul 21, 2026

Copy link
Copy Markdown
Contributor

Previously, when git signing failed (due to non-interactive environments etc),
the git commit would be aborted.

With this change, it allows you to retry with signing disabled.


Note

Medium Risk
Touches commit execution, error classification, and RPC contracts across server and clients; incorrect signing detection could mis-prompt retries, but unsigned retry is explicit and scoped per attempt.

Overview
When a stacked git commit fails because GPG/SSH signing cannot run (common in non-interactive environments), clients can retry the same action with signing disabled instead of stopping cold.

The server classifies signing failures from commit stderr (with hook failures excluded), surfaces failureKind: commit_signing_failed on progress/errors, and runs git commit --no-gpg-sign when disableCommitSigning is set. Unsigned retries after a feature branch was already created do not create another branch. Hook progress attribution during commits is tightened so multi-hook output is not mislabeled.

Web shows a “Retry without signing” action on the error toast; mobile shows the same choice via Alert. buildUnsignedCommitRetryInput keeps action, message, and file paths while forcing the unsigned flag.

Reviewed by Cursor Bugbot for commit 1ebb4e4. Bugbot is set up for automated code reviews on this repo. Configure here.

Note

Allow retrying git commits without signing when commit signing fails

  • Adds isCommitSigningFailure detection by matching GPG, pinentry, and SSH signer error patterns in commit stderr output in GitVcsDriverCore.ts.
  • Introduces a failureKind field ('unknown' | 'commit_signing_failed') on GitCommandError and action_failed progress events, with a default of 'unknown' for backwards compatibility.
  • On a signing failure, the web UI (GitActionsControl.tsx) shows a "Retry without signing" button in the error toast; the mobile client (use-selected-thread-git-actions.ts) shows a native Alert with the same retry option.
  • buildUnsignedCommitRetryInput constructs a retry payload with disableCommitSigning: true while preserving the original action, commit message, and file paths.
  • Adds --no-gpg-sign to the git commit invocation when disableCommitSigning is set, propagated from the contract layer through the server to the git core.

Macroscope summarized 1ebb4e4.

@github-actions github-actions Bot added vouch:unvouched PR author is not yet trusted in the VOUCHED list. size:L 100-499 changed lines (additions + deletions). labels Jul 21, 2026
@coderabbitai

coderabbitai Bot commented Jul 21, 2026

Copy link
Copy Markdown

Important

Review skipped

Auto reviews are disabled on this repository. Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

⚙️ Run configuration

Configuration used: Repository UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 442e53a5-de8a-4b9f-ba89-2c138936ccfc

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@tim-smart tim-smart changed the title Allow retrying git commits with signing when signing fails Allow retrying git commits without signing when signing fails Jul 21, 2026
Comment thread apps/mobile/src/state/use-selected-thread-git-actions.ts
Comment thread packages/contracts/src/git.ts
Comment thread apps/mobile/src/state/use-selected-thread-git-actions.ts Outdated
Comment thread packages/contracts/src/git.ts
@macroscopeapp

macroscopeapp Bot commented Jul 21, 2026

Copy link
Copy Markdown
Contributor

Approvability

Verdict: Needs human review

This PR introduces a new feature with user-facing dialogs and recovery workflows for commit signing failures. The changes span mobile, web, and server layers with new error classification logic and a disableCommitSigning flag propagated throughout the stack, warranting human review.

You can customize Macroscope's approvability policy. Learn more.

Comment thread apps/server/src/git/GitManager.ts
@tim-smart
tim-smart force-pushed the t3code/git-signing-toggle branch 2 times, most recently from 2de8119 to 779bf4e Compare July 22, 2026 21:13

@cursor cursor Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes using high effort and found 3 potential issues.

Fix All in Cursor

❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.

Reviewed by Cursor Bugbot for commit 779bf4e. Configure here.

const failure: E | VcsActionRemoteFailureError =
terminal?.kind === "action_failed" ? remoteFailure(terminal) : error;
return Effect.fail<E | VcsActionRemoteFailureError>(failure);
}),

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Success lost after stream error

Medium Severity

The new Effect.catch prefers a terminal action_failed over a trailing stream error, but still fails when action_finished was already received. A successful stacked action (including an unsigned retry) can surface as a failure if the RPC stream errors after the terminal event, so the UI can prompt another attempt and create a duplicate commit.

Fix in Cursor Fix in Web

Reviewed by Cursor Bugbot for commit 779bf4e. Configure here.

});
currentHookName = null;
}
yield* finalizeUnattributedOutput(sawCommitHook);

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hookless failures hide git stderr

Medium Severity

Unattributed commit output is buffered while no hook is active, then flushed only when sawCommitHook is true. In repos without commit hooks, non-signing commit failures never emit those stderr lines as progress, so the UI keeps a generic “Git command exited with a non-zero status” message instead of the underlying git diagnostic.

Additional Locations (1)
Fix in Cursor Fix in Web

Reviewed by Cursor Bugbot for commit 779bf4e. Configure here.

disableCommitSigning: true,
skipDefaultBranchPrompt: true,
progressToastId: resolvedProgressToastId,
});

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Web retry skips branch sync

Medium Severity

Unsigned retry after a featureBranch signing failure omits featureBranch, so a successful retry returns branch.status: "skipped_not_requested". Web only syncs thread metadata via syncThreadBranchAfterGitAction when a branch was created in that same result, and this retry path does not refresh status or sync the current ref. Mobile handles this with syncCurrentBranchOnSuccess, so web can leave the thread on the old branch while git is already on the feature branch.

Additional Locations (2)
Fix in Cursor Fix in Web

Reviewed by Cursor Bugbot for commit 779bf4e. Configure here.

- Detect commit signing failures across server and client
- Let stacked git actions retry once with signing disabled
- Preserve unsigned commit behavior in commit, push, and PR flows
- Prevent stale action controls from appearing on Git progress toasts
@tim-smart
tim-smart force-pushed the t3code/git-signing-toggle branch from 779bf4e to 1ebb4e4 Compare July 23, 2026 01:09
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

size:L 100-499 changed lines (additions + deletions). vouch:unvouched PR author is not yet trusted in the VOUCHED list.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant